﻿using CyberConnect.Insteon.Messaging;
using System;

namespace CyberConnect.Insteon.Devices
{
    public class InsteonDevice : IInsteonDevice
    {
        private readonly DeviceAddress _Address;

        /// <summary>
        /// The DeviceAddress of the InsteonDevice.
        /// </summary>
        public DeviceAddress Address { get { return _Address; } }

        private readonly byte _Category;

        /// <summary>
        /// The category the InsteonDevice is defined under.
        /// </summary>
        public byte Category { get { return _Category; } }

        private readonly byte _Subcategory;

        /// <summary>
        /// The subcategory the InsteonDevice is defined under.
        /// </summary>
        public byte Subcategory { get { return _Subcategory; } }

        public InsteonDevice(DeviceAddress address, byte category, byte subcategory)
        {
            this._Address = address;
            this._Category = category;
            this._Subcategory = subcategory;
        }

        /// <summary>
        /// Sends a ping command to a device.
        /// </summary>
        /// <param name="link">The PLM that will send the request.</param>
        /// <param name="device">The InsteonDevice to ping.</param>
        public static void Ping(PlmLinc link, InsteonDevice device)
        {
            if (device == null) { throw new ArgumentNullException("device"); }

            InsteonDevice.Ping(link, device.Address);
        }

        /// <summary>
        /// Sends a ping command to a device.
        /// </summary>
        /// <param name="link">The PLM that will send the request.</param>
        /// <param name="address">The DeviceAddress to ping.</param>
        public static void Ping(PlmLinc link, DeviceAddress address)
        {
            if (link == null) { throw new ArgumentNullException("link"); }

            link.PingDevice(address);
        }

        /// <summary>
        /// Sends a ping command to this device.
        /// </summary>
        /// <param name="link">The PLM that will send the request.</param>
        public void Ping(PlmLinc link)
        {
            InsteonDevice.Ping(link, this);
        }

        /// <summary>
        /// Provides a human-readable identification string.
        /// </summary>
        /// <returns>Device type followed by the device's address.</returns>
        public override string ToString()
        {
            return DeviceIdentification.GetDeviceName(_Category, _Subcategory) + " @ " + _Address.ToString();
        }
    }
}